Mapping Identifiers for Sitecore Data Providers
When external content is exposed via a data provider, the content is represented by a Sitecore item. Every Sitecore item has an ID. It is likely that the content in the external system also has a unique identifier. Being able to map a Sitecore item ID to the unique identifier in the external system is an important part of building a data provider.
The following are common options for handing this mapping:
- IDTable - assigning a GUID for an external identifier
- Deterministic GUIDs - generating a GUID using an external identifier
IDTable
Sitecore provides a storage area called the IDTable where external identifiers can be mapped to Sitecore item IDs.
- API - describes the API used to interact with the IDTable
- Caching - describes the IDTable caching features
- IDTableProvider - the provider responsible for storing data in and retrieving data from the IDTable.
API
Sitecore has an API that is dedicated to mapping identifiers to Sitecore item IDs. The API is found in the namespace Sitecore.Data.IDTables
.
Using the API requires you understand a few concepts:
- Key - the unique identifier of a resource in an external data source. A key is stored as a string value
- Prefix - a string that uniquely identifies an external data source. A single IDTable may store mappings for multiple external data sources. The combination of the prefix and the key uniquely identify an external resource in the IDTable.
- ID - Sitecore item ID that is mapped to a combination of Prefix and Key
- Parent ID - Sitecore item ID for the parent item of the Sitecore item identified by the ID
- Custom Data - a string that contains extra information relevant to mapping an external identifier to an ID
- Entry - a “record” from the IDTable. An entry includes the key, prefix and ID.
The following code samples demonstrate how to work with the IDTable API:
- Add an entry
- Add an entry (specifying Parent ID)
- Add an entry (specifying Custom Data)
- Get an entry from a combination of Prefix and Key
- Get an entry from a combination of Prefix and ID
- Get the entries for a Prefix
- Remove an entry using a Prefix and Key
- Remove an entry using a Prefix and ID
- Update an entry
Add an entry
var prefix = "source1";
var key = "product1";
var newId = Sitecore.Data.ID.Parse("{5D31DF26-9562-47E0-8095-666BD681AD08}");
var entry = IDTable.Add(prefix, key, newId);
Add an entry (specifying the Parent ID)
var prefix = "source1";
var key = "product1";
var newId = Sitecore.Data.ID.Parse("{5D31DF26-9562-47E0-8095-666BD681AD08}");
var parentId = Sitecore.Data.ID.Parse("{1E7B9470-06CC-4E59-B8F5-9CD221454E71}");
var entry = IDTable.Add(prefix, key, newId, parentId);
Add an entry (specifying the Custom Data)
var prefix = "source1";
var key = "product1";
var newId = Sitecore.Data.ID.Parse("{5D31DF26-9562-47E0-8095-666BD681AD08}");
var parentId = Sitecore.Data.ID.Parse("{1E7B9470-06CC-4E59-B8F5-9CD221454E71}");
var customData = "name=Something|place=Here";
var entry = IDTable.Add(prefix, key, newId, parentId, customData);
Get an entry from a combination of Prefix and Key
var prefix = "source1";
var key = "product1";
var entry = IDTable.GetID(prefix, key);
Get an entry from a combination of Prefix and ID
var prefix = "source1";
var id = Sitecore.Data.ID.Parse("{5D31DF26-9562-47E0-8095-666BD681AD08}");
var entry = IDTable.GetKeys(prefix, id).FirstOrDefault();
Get the entries for a Prefix
var prefix = "source1";
var key = "product1";
var entries = IDTable.GetKeys(prefix);
Remove an entry using a Prefix and Key
var prefix = "source1";
var key = "product1";
IDTable.RemoveKey(prefix, key);
Remove an entry using a Prefix and ID
var prefix = "source1";
var id = Sitecore.Data.ID.Parse("{5D31DF26-9562-47E0-8095-666BD681AD08}");
IDTable.RemoveID(prefix, id);
Update an entry
There is no API for updating an entry, so an entry must be removed and then added.
var prefix = "source1";
var key = "product1";
var id = Sitecore.Data.ID.Parse("{5D31DF26-9562-47E0-8095-666BD681AD08}");
IDTable.RemoveID(prefix, id);
var customData = "name=Something|place=Here";
var entry = IDTable.Add(prefix, key, id, Sitecore.Data.ID.Null, customData);
IDTableProvider
Sitecore must store the mappings somewhere. This is handled by a provider that inherits from Sitecore.Data.IDTables.IDTableProvider
.
The default provider uses a relational database table to store the mappings. This table is named IDTable
. The IDTable configuration identifies which relational database is used. By default Sitecore uses the relational database that corresponds to the connection string named master
:
<IDTable type="Sitecore.Data.$(database).$(database)IDTable, Sitecore.Kernel" singleInstance="true">
<param connectionStringName="master" />
<param desc="cacheSize">2500KB</param>
</IDTable>
The default provider implements some additional features:
Caching
The default IDTable provider uses implements its own caching. The size of the cache is specified in the IDTable configuration.
<IDTable type="Sitecore.Data.$(database).$(database)IDTable, Sitecore.Kernel" singleInstance="true">
<param connectionStringName="master" />
<param desc="cacheSize">2500KB</param>
</IDTable>
Events
The default IDTable provider triggers the following events:
- idtable:added - when an entry is added to the IDTable
- idtable:removed - when an entry is removed from the IDTable
Deterministic GUIDs
It is possible to generate a GUID using a string. The algorithm is described in RFC4122 from the IETF.
A C# implementation of the algorithm is available on GitHub.
The following demonstrates how to use this implementation. The GUID {9D02E821-E902-5BA1-BE5E-3B3F87F2DB51}
will always returned when the external identifier D-7734J
is supplied.
var externalId = "D-7734J";
var guid = GuidUtility.Create(GuidUtility.IsoOidNamespace, externalId);
Use the following code to check if a specific GUID corresponds to an external identifier:
var guidExpected = Guid.Parse("{9D02E821-E902-5BA1-BE5E-3B3F87F2DB51}");
var externalId = "D-7734J";
var guidCreated = GuidUtility.Create(GuidUtility.IsoOidNamespace, externalId);
var match = (guidExpected == guidCreated);